
import { GameplayComponent } from "../../GameplayComponent";
import ViewGameplay from "../../ViewGameplay";
import { GpWorldLayer } from "../GpWorld";
import GpEff, { GpEffProp } from "./GpEff";
import { Sglt } from "../../m/SgltDefine";
import { GpEventDef } from "../../m/GpEventDef";
import { PlayEffEventData } from "../../m/GpDef";
import { Comp } from "../../m/CompDef";


import { _decorator, Component, Node, Vec2, Vec3, isValid } from 'cc';
import { NodePoolMap } from "../../../../../extensions/cocos-scaffold-3x/assets/ui/NodePoolMap";
import { EBundleName, gg } from "../../../../Game";
import { EcsEntity } from "ecs-ts";
const { ccclass, property } = _decorator;

@ccclass
export default class GpEffMaker extends GameplayComponent<ViewGameplay>{



    poolMap: NodePoolMap = null

    onInit(): void {
        this.poolMap = new NodePoolMap("GpEff",EBundleName.subBundle)
        const gpWorld = this.prop.gpWorld
        const ecsWorld = gpWorld.prop.ecsWorld
        const worldInfo = gpWorld.prop.ecsWorld.getSingleton(Sglt.WorldInfo)


        gg.eventTarget.on(GpEventDef.playEff, async (data: PlayEffEventData) => {
            if (data.target) {
                const gpEntity = this.prop.gpWorld.entityMap.get(data.target.id)
                if (gpEntity) {
                    const effPath = data.logic.data[0]
                    this.addEff(`gameplay/v/eff/spine/${effPath}`, gpEntity.node.position)
                }
            }
        }, this)
    }


    /**
     * 移除特效
     * @param eff 
     */
    removeEff(eff: GpEff) {
        this.poolMap.backNode(eff.node, eff.prop.path)
    }

    /**
     * 添加特效
     * @param path 特效路径
     * @param pos 位置
     * @param followEntity 跟随实体
     * @param duration 持续时间
     * @param layer 层级
     * @param onMake 特效创建回调
     * @returns 
     */
    async addEff(path: string, pos: Vec2 | Vec3, followEntity?: EcsEntity, duration?: number, layer: GpWorldLayer | Node = GpWorldLayer.unit, onMake?: (effNode: Node) => void) {
        const eff = await this.poolMap.makeNode(path)
        if (!eff) {
            return
        }
        if (!isValid(this.node, true)) {
            return
        }
        onMake?.(eff)
        eff.setPosition(pos.x, pos.y)
        eff.getComponent(GpEff)?.init(new GpEffProp(this, path, followEntity, duration))
        this.prop.gpWorld.addNodeOnLayer(eff, layer)
        return eff
    }

    protected onDestroy(): void {
        this.unscheduleAllCallbacks()
        gg.eventTarget.targetOff(this)
    }
}